#ifndef MY_SHELL_PARSER_H
#define MY_SHELL_PARSER_H

#include <vector>
#include <cstdint>
#include <memory>

#include "MyShellNamespace.h"
#include "MyShellGrammarNode.h"

MY_SHELL_NAMESPACE_BEGIN
// 语法分析器
class MyShellParser
{
private:
    // 要分析的单词序列
    static std::vector<mysh::Word> words;
    // 所需分析的单词序列中单词的数量
    static std::size_t word_num;
    // 当前分析的单词的索引
    static std::int32_t cur_index;
public:
    // 删除所有构造及析构函数
    MyShellParser() = delete;
    MyShellParser(const mysh::MyShellParser& other) = delete;
    MyShellParser(mysh::MyShellParser&& other) = delete;
    ~MyShellParser() = delete;
private:
    // 辅助语法分析的函数
    // 分析声明语句
    static std::shared_ptr<mysh::DeclareStatementNode> parseDeclareStatement();
    // 分析运行语句
    static std::shared_ptr<mysh::RunStatementNode> parseRunStatement();
    // 分析输入输出语句
    static std::shared_ptr<mysh::InputOutputStatementNode> parseInputOutputStatement();
    // 分析左值节点
    static std::shared_ptr<mysh::LeftValueNode> parseLeftValueNode();
    // 分析数值节点
    static std::shared_ptr<mysh::DataNode> parseDataNode();
    // 分析赋值语句
    static std::shared_ptr<mysh::AssignStatementNode> parseAssignStatement();
    // 分析条件节点
    static std::shared_ptr<mysh::GrammarNode> parseConditionNode();
    // 分析if-else语句块
    static std::shared_ptr<mysh::IfElseStatementBlock> parseIfElseStatementBlock();
    // 分析for语句块
    static std::shared_ptr<mysh::GrammarNode> parseForStatementBlock();
    // 分析语句块内的语句
    static std::vector<std::shared_ptr<mysh::GrammarNode>> parseStatementsInBlock();
public:
    // 语法分析主入口
    static std::vector<std::shared_ptr<mysh::GrammarNode>> parse(const std::vector<mysh::Word>& words);
private:
    // 辅助打印的函数
    // 打印缩进
    static std::ostream& printIndentation(const std::int32_t& indentation);
    // 打印声明语句信息
    static void printDeclareStatementMessage(const std::shared_ptr<mysh::DeclareStatementNode>& declare_statement_node, std::int32_t indentation);
    // 打印运行语句信息
    static void printRunStatementMessage(const std::shared_ptr<mysh::RunStatementNode>& run_statement_node, std::int32_t indentation);
    // 打印输入输出语句信息
    static void printInputOutputStatementMessage(const std::shared_ptr<mysh::InputOutputStatementNode>& io_statement_node, std::int32_t indentation);
    // 打印左值节点
    static void printLeftValueNode(const std::shared_ptr<mysh::LeftValueNode>& left_value_node, std::int32_t indentation);
    // 打印数值节点
    static void printDataNode(const std::shared_ptr<mysh::DataNode>& data_node, std::int32_t indentation);
    // 打印赋值语句信息
    static void printAssignStatementMessage(const std::shared_ptr<mysh::AssignStatementNode>& assign_statement_node, std::int32_t indentation);
    // 打印if-else语句块信息
    static void printIfElseStatementBlockMessage(const std::shared_ptr<mysh::IfElseStatementBlock>& if_else_statement_block, std::int32_t indentation);
    // 打印for-in语句块信息
    static void printForInStatementBlockMessage(const std::shared_ptr<mysh::ForInStatementBlock>& for_in_statement_block, std::int32_t indentation);
    // 打印for-to语句块信息
    static void printForToStatementBlockMessage(const std::shared_ptr<mysh::ForToStatementBlock>& for_to_statement_block, std::int32_t indentation);
public:
    // 外部可用其它接口
    // 打印语法分析所有信息
    static void printParseMessage(const std::vector<std::shared_ptr<mysh::GrammarNode>>& all_grammar_nodes, std::int32_t indentation = 0);
};
MY_SHELL_NAMESPACE_END

#endif // ! MY_SHELL_PARSER_H